#pragma once

#include "ShmBlock.h"
#include "LinkedList.h"
#include "IodpModule.h"

template <typename T, typename CLock = CFakeLock>
class CClientList : public CLinkedList<T, CLock>
{
    typedef typename CLinkedList<T, CLock>::Node BaseNode;

public:
    struct ListNode : public BaseNode
    {
        friend class CClientList;

    private:
        void *operator new(size_t sz)
        {
            void *ptr = nullptr;
            CShmBlock *pShmPtr = CIodpModule::GetShmBlock();

            if (nullptr != pShmPtr)
                ptr = pShmPtr->Alloc(sz);

            return ptr;
        }

        void *operator new(size_t sz, int iExt)
        {
            void *ptr = nullptr;
            CShmBlock *pShmPtr = CIodpModule::GetShmBlock();

            if (nullptr != pShmPtr)
                ptr = pShmPtr->Alloc(sz + iExt);

            return ptr;
        }

        void *operator new(size_t, void *ptr) _GLIBCXX_USE_NOEXCEPT { return ptr; }

        void operator delete(void *ptr)
        {
            CShmBlock *pShmPtr = CIodpModule::GetShmBlock();

            if (nullptr != pShmPtr)
                pShmPtr->Free(ptr);
        }
    };

public:
    BaseNode *NewNode()
    {
        return new ListNode();
    }

    BaseNode *NewNode(int iExtLen)
    {
        return new (iExtLen) ListNode();
    }

    BaseNode *NewNode(void *ptr)
    {
        if (nullptr == ptr)
            return nullptr;

        return new (ptr) ListNode();
    }

    void DeleteNode(BaseNode *pNode)
    {
        // 自动调用Node及其父结构的析构函数,父结构需虚析构函数
        delete (ListNode *)pNode;
    }
};
